Hello, 各位 iT 邦幫忙 的粉絲們大家好~~~
在本系列文因為工作上的產品應用需求,進而探索到很多層面的點滴事。
透過每篇 EP 的分享把這些點滴整理,看起來或許像是個獨立的小品抒發文、也或許是一系列技術研究文!?
總之,就當作的隨手雜記文吧!
本篇是 莫名其妙就跟世界等級的 OpenSource 專案攪和了!? 系列文的 EP27。
在經過 EP26 的介紹中已能成功在 GstreamerPlayer 專案當中整合使用自建的 "gstreamer-sharp.dll", "gio-sharp.dll", "glib-sharp.dll" 來播放影片。
可是面臨到的問題卻變成,GstreamerPlayer 專案的程式一但開始播放影片就會莫名其妙地狂佔用記憶體,直到記憶體資源耗盡,最後會被系統強迫停止。
是 MSVC 的 Gstreamer 問題?
透過 EP09 介紹的 Gstreame pipline 指令測試看看:
gst-launch-1.0 filesrc location="c:/tmp/bbb_sunflower.mp4" ! decodebin ! autovideosink
順利播放影片沒問題:
打開 Windows 工作管理員來看看記憶體的耗用量:
看起來不是!
那問題就會是指向自建的 "gstreamer-sharp.dll", "gio-sharp.dll", "glib-sharp.dll" 這三個 dll 了。
那...
回頭觀察了一下原本 GstreamerPlayer 還沒換成使用自建 DLLs 的時候,所使用的 gstreamer-netcore 專案。
這裡是當初 vladkol 作者撰寫此專案時所加入的程式碼:
這裡是為了使用 glib-sharp、gio-sharp 所引用的公開 nuget 套件的參考:
而這裡卻是直接使用 gstreamer-sharp 的程式碼:
看到這裡的時候,很納悶為什麼要這樣做?
就算沒有公開的 nuget 套件可以直接在專案引用,也能直接引用編譯好的 gstreamer-sharp.dll 就好,為何特地要把 gstreamer-sharp 的 source code 直接放在專案當中使用?
但至少...
目前 gstreamer-netcore 是個可供參考的對象;畢竟會 memory leak 跟會 memory explosion,可能前者還比較好一點。
把 gstreamer 的 source code 抓回來對照。
經過一段為期不短的咒語術式精神時光屋鍛鍊後,終於在 gstreamer 的 source code 針對 gstreamer-sharp 的部分找到一個很弔詭的地方。
為何在 Gst.MiniObject 的類別 Ref 、 Unref 、 DisposeUnmanagedFunc 這三個 meathods 被移除掉了?
那既然這裡 Gst.MiniObject 的類別不設計這三個方法的 override 那就子類別要自己實作囉?
然後再追看下去所有繼承自 Gst.MiniObject 的類別,有 Buffer、Caps、Memory、Message...等。
這幾個播放影片時會用到的類別的 Ref、Unref、DisposeUnmanagedFunc 的這三個 methods 也都在同一個 commit 時被移除了??
那...
往 Gst.MiniObject 的所繼承的 GLib.Opaque 上層類別看看:
(注意:這個類別是屬於 glab-sharp.dll 的)
Ref 、 Unref 是設計成 virtual 的方法,有實作但並沒有任何處理的程式碼耶!
雖然 對整個 gstreamer 的 source code 並沒有很全盤的了解,但不是很能理解為什麼會進行這樣的異動。
Look at my eyes!
Tell me, why?
why? baby why?
(正確的英文語法應為:Look me in the eyes and tell me why!)
而且光看 method 的名稱 "Ref"、"Unref" 就令人不禁懷疑在播放影片後會記憶體就爆衝的問題在這裡。